package cn.xk.ymcc.service.impl;

import cn.xk.ymcc.domain.CourseType;
import cn.xk.ymcc.mapper.CourseTypeMapper;
import cn.xk.ymcc.service.ICourseTypeService;
import com.baomidou.mybatisplus.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * <p>
 * 课程目录 服务实现类
 * </p>
 *
 * @author 64009120@qq.com
 * @since 2023-03-11
 */
@Service
public class CourseTypeServiceImpl extends ServiceImpl<CourseTypeMapper, CourseType> implements ICourseTypeService {
    @Autowired
    private RedisTemplate<Object, Object> redisTemplate;

     /*
        增删改数据库里面数据的改变引发问题？
        数据库发生改变，redis里面也要发生改变
        解决方案：重写 增删改方法
            简单的做法：增删改以后把redis里面的数据删了
     */

    @Override
    @CacheEvict(cacheNames = "cache",key = "'ALL'")
    public boolean insert(CourseType entity) {
        return super.insert(entity);
    }

    @Override
    public boolean deleteById(Serializable id) {
        boolean b = super.deleteById(id);
        if (b) redisTemplate.delete("treeData");
        return b;
    }

    @Override
    public boolean updateById(CourseType entity) {
        boolean b = super.updateById(entity);
        if (b) redisTemplate.delete("treeData");
        return b;
    }

    @Override
    @Cacheable(cacheNames = "cache",key = "'ALL'")
    public List<CourseType> goTreeData() {
        List<CourseType> treeDate = (List<CourseType>) redisTemplate.opsForValue().get("treeDate");
        if (treeDate == null) {   //1.先查询所有的数据,从redis当中没查到数据
            return treeDataInDb();
        }
        return treeDate;
    }

    private List<CourseType> treeDataInDb() {
        List<CourseType> treeDatas = new ArrayList<>();
        //1.先查询所有数据
        List<CourseType> courseTypes = super.selectList(null);
        //2.转化为一个Map
        /*Map<Long, CourseType> map = new HashMap<>();*/
        Map<Long, CourseType> map = courseTypes.stream().collect(Collectors.toMap(CourseType::getId, courseType -> courseType));
        //3.准备一个返回的集合
        for (CourseType courseType : courseTypes) {
            if (courseType.getPid() == null || courseType.getPid() == 0) {
                treeDatas.add(courseType);
            } else { //4.2 不是顶层分类，找到当前分类的父级分类，再把当前的分类放到父类分类的儿子下面
                map.get(courseType.getPid()).getChildren().add(courseType);
            }
        }
        redisTemplate.opsForValue().set("treeDatas", treeDatas);
        return treeDatas;
    }
}

